const WorkerService = require('../service/worker');
const SendService = require('../service/sendRecordService');
const TenantService = require('../service/tenant');
const ContractService = require('../service/contract');
const WorkerSignRecordService = require('../service/workerSignRecordService');
// const noticeService = require('../service/notice');

const { cloudApiClient, mergeAgent, logger } = require('../utils');
const { v4 } = require('uuid');

const workerService = new WorkerService();
const sendService = new SendService();
const tenantService = new TenantService();
const contractService = new ContractService();
const workerSignRecordService = new WorkerSignRecordService();
const _ = require('lodash');

const getAgent = async req => {
  const { userInfo } = req;
  const targetUser = userInfo;
  if (!targetUser) {
    console.error('targetUser: not found');
    return false;
  }
  return {
    ...mergeAgent({
      ProxyOrganizationOpenId: targetUser.organizationId,
      OpenId: targetUser.openId,
      ProxyAppId: targetUser.proxyAppId,
    }),
    OrganizationName: targetUser.organizationName,
    UserId: targetUser.userId,
    UserName: targetUser.userName,
  };
};
const statusMap = {
  WAIT_SEND: 'ALL',
  ALL: 'ALL',
};
module.exports = app => {
  // 根据状态统计图表数据
  app.get(`${process.env.VUE_APP_BASE_API}/worker/statistics/byStatus`, async (req, res) => {
    const { userInfo } = req;
    if (!userInfo) {
      return res.json({ code: 50000, message: '未登录' });
    }
    const workerList = await workerService.filter({
      organizationId: userInfo.organizationId,
    });

    const sendList = await sendService.list();

    const tenantList = await tenantService.filter({ organizationId: userInfo.organizationId });

    // 总派遣情况
    const tenantWaitSends = tenantList.map(tItem => {
      const sendCount = sendList.filter(wItem => wItem.tenantId === tItem.id && wItem.status === 'SEND').length;
      return {
        ...tItem,
        sendCount,
      };
    });

    // 当前派遣情况
    const obj = {};
    const group = _.groupBy(workerList, 'status');

    // eslint-disable-next-line no-restricted-syntax
    for (const key in group) {
      obj[key] = group[key].length;
    }

    return res.json({
      code: 20000,
      data: {
        currentSend: obj,
        tenantWaitSends,
      },
    });
  });

  app.post(`${process.env.VUE_APP_BASE_API}/worker/list`, async (req, res) => {
    const { body = {}, userInfo } = req;
    const { limit = 10, offset = 0, name, mobile, proposalStatus, status } = body;
    if (userInfo) {
      try {
        const listParam = {
          organizationId: userInfo.organizationId,
        };
        if (status !== undefined) {
          listParam.status = statusMap[status] || status;
        }
        if (proposalStatus !== undefined) { // 安全承诺书状态筛选
          listParam.proposalStatus = proposalStatus;
        }

        const list = await workerService.search({
          where: listParam,
          offset,
          limit,
          name,
          mobile,
        });

        const totalCount = await workerService.searchCount({
          where: listParam,
          name,
          mobile,
        });

        if (status === 'SEND') {
          // 派遣状态需要查派遣表和用工单位表
          await Promise.all(
            list.map(item =>
              sendService
                .search({
                  where: {
                    workerId: item.id,
                  } })
                .then(sendList => {
                  if (sendList?.length) {
                    const latestRecord = sendList[sendList.length - 1];
                    item.sendStartTime = latestRecord?.startTime;
                    item.sendEndTime = latestRecord?.endTime;
                    item.sendId = latestRecord.id || latestRecord.Id;
                    return tenantService.find(latestRecord.tenantId).then(tenant => {
                      if (tenant) {
                        item.tenantName = tenant.name;
                      }
                    });
                  }
                }),
            ),
          );
        }
        if (status) {
          await Promise.all(
            list.map(item =>
              workerSignRecordService
                .search({ where: { workerId: item.id, type: 'work-contract' } })
                .then(contractList => {
                  if (contractList?.length) {
                    const latestRecord = contractList[contractList.length - 1];
                    return contractService.find(latestRecord.contractId).then(contract => {
                      item.contractName = contract.FlowName;
                      item.contractId = contract.FlowId;
                      item.deadline = contract.DeadLine;
                      item.contractStatus = contract.FlowStatus;
                    });
                  }
                }),
            ),
          );
        }
        return res.json({
          code: 20000,
          data: { workers: list, totalCount },
        });
      } catch (error) {
        logger.error({
          action: 'worker/list',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '数据查询失败',
        });
      }
    }
    logger.error({
      action: 'worker/list',
      data: body,
      errMessage: '用户登录已过期',
    });
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });

  app.post(`${process.env.VUE_APP_BASE_API}/worker/detail`, async (req, res) => {
    const { body = {}, userInfo } = req;
    const { Id } = body;
    if (userInfo) {
      try {
        const worker = await workerService.find(Id);
        const contractRecords = [];
        const workerSignList = await workerSignRecordService.search({ where: { workerId: Id, type: 'work-contract' }, offset: 0, limit: 3 });
        const workerSignCount = await workerSignRecordService.searchCount({ workerId: Id, type: 'work-contract' });
        if (workerSignList) {
          await Promise.all(
            workerSignList.map(record =>
              contractService.find(record.contractId).then(flowInfo => {
                // eslint-disable-next-line operator-linebreak
                flowInfo &&
                  contractRecords.push({
                    contractId: flowInfo.FlowId,
                    deadline: flowInfo.DeadLine,
                    status: record.status,
                    createdOn: flowInfo.CreateOn,
                    contractName: flowInfo.FlowName,
                  });
              }),
            ),
          );
        }
        worker.contractList = contractRecords;
        worker.contractAmount = workerSignCount;
        return res.json({
          code: 20000,
          data: { worker },
        });
      } catch (error) {
        logger.error({
          action: 'worker/detail',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '工人信息查询失败',
        });
      }
    }
    logger.error({
      action: 'worker/detail',
      data: body,
      errMessage: '用户登录已过期',
    });
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });

  app.post(`${process.env.VUE_APP_BASE_API}/worker/create`, async (req, res) => {
    const { userInfo, body } = req;
    const { name, idcardNo, mobile } = body;
    if (userInfo) {
      try {
        const condition = {
          organizationId: userInfo.organizationId,
        };
        if (idcardNo) {
          condition.idcardNo = idcardNo;
        } else {
          Object.assign(condition, { mobile });
        }
        const oldWorker = await workerService.first(condition);
        if (oldWorker) {
          return res.json({
            code: 500,
            message: `工人${name}(${idcardNo ? '身份证' : '手机号'}：${idcardNo || mobile})已存在`,
          });
        }
        const newWorker = await workerService.create({
          ...body,
          creatorOpenId: userInfo.openId,
          organizationId: userInfo.organizationId,
        });
        if (newWorker) {
          return res.json({
            code: 20000,
            data: { worker: newWorker, Id: newWorker.id },
          });
        }
        return res.json({
          code: 500,
          message: '工人添加失败',
        });
      } catch (error) {
        logger.error({
          action: 'worker/create',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '工人添加失败',
        });
      }
    }
    logger.error({
      action: 'worker/create',
      data: body,
      errMessage: '用户登录已过期',
    });
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });
  // deleteById
  app.post(`${process.env.VUE_APP_BASE_API}/worker/deleteById`, async (req, res) => {
    const { body, userInfo } = req;
    if (userInfo) {
      try {
        const status = await workerService.clean(body.Id);
        // const workerSendRecords = await sendService.filter({ workerId: body.Id }); // 工人派遣记录
        // const workerSignRecords = await workerSignRecordService.filter({ workerId: body.Id }); // 工人签署记录
        // await Promise.all(workerSendRecords.map(item => sendService.delete(item.id))); // 删除派遣记录
        // for (const item of workerSignRecords) {
        //   await contractService.delete(item.contractId); // 删除合同
        //   await workerSignRecordService.delete(item.id); // 删除工人合同签署记录
        // }
        if (status === 0) {
          return res.json({
            code: 20000,
            data: { Id: body.Id },
          });
        }
        return res.json({
          code: 500,
          message: '删除失败',
        });
      } catch (error) {
        logger.error({
          action: 'worker/deleteById',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '删除失败',
        });
      }
    }
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });

  app.post(`${process.env.VUE_APP_BASE_API}/worker/update`, async (req, res) => {
    const { userInfo, body } = req;
    const { name, mobile, idcardNo } = body;

    if (userInfo) {
      try {
        if (name && mobile) {
          const condition = {
            organizationId: userInfo.organizationId,
          };
          if (idcardNo) {
            condition.idcardNo = idcardNo;
          } else if (mobile) {
            Object.assign(condition, { mobile });
          }
          const oldWorker = await workerService.first(condition);
          if (oldWorker && oldWorker.id !== body.id) {
            return res.json({
              code: 500,
              message: `工人${name}(${idcardNo ? '身份证' : '手机号'}：${idcardNo || mobile})已存在`,
            });
          }
        }

        const status = await workerService.update(body.id, body);
        if (status) {
          return res.json({
            code: 20000,
            data: { Id: body.id },
          });
        }
        return res.json({
          code: 500,
          message: '修改工人信息失败',
        });
      } catch (error) {
        logger.error({
          action: 'worker/deleteById',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '修改工人信息失败',
        });
      }
    }
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });

  // 发起工人劳务合同
  app.post(`${process.env.VUE_APP_BASE_API}/worker/createContracts`, async (req, res) => {
    const { body, userInfo } = req;
    const { UserName, UserId, ...agent } = await getAgent(req);
    const { flowInfos, needPreview = false, previewType = 1 } = body;

    if (agent) {
      const params = {
        Agent: agent,
        Version: '2021-05-26',
        // ...body,
        FlowInfos: flowInfos,
        NeedPreview: needPreview,
        PreviewType: previewType || 1,
      };
      params.FlowInfos.forEach(v => {
        v.FlowApprovers[0].OpenId = userInfo.openId;
        v.FlowApprovers[0].OrganizationOpenId = userInfo.organizationOpenId;
        v.FlowApprovers[1].JumpUrl = 'https://channel-demo.test.ess.tencent.cn/m/transitionPage'; // 工人签署完成后跳转地址
      });

      try {
        const flowRes = await cloudApiClient.CreateFlowsByTemplates(params);
        logger.info({
          action: 'worker/createContracts',
          data: { flowRes, params },
        });

        if (flowRes.ErrorMessages && flowRes.ErrorMessages.length && flowRes.ErrorMessages?.[0]) {
          logger.error({
            action: 'worker/createContracts',
            data: body,
            errMessage: flowRes.ErrorMessages,
          });
          return res.json({
            code: 50000,
            message: flowRes.ErrorMessages.join(','),
          });
        }

        // 预览模式下不存储数据
        if (needPreview) {
          return res.json({ code: 20000, data: flowRes });
        }

        if (flowRes?.FlowIds?.length) {
          const startDate = flowInfos?.[0]?.FormFields.find(f => f.ComponentName === 'starttime')?.ComponentValue;
          const endDate = flowInfos?.[0]?.FormFields.find(f => f.ComponentName === 'endtime')?.ComponentValue;
          const monthlyPay = flowInfos?.[0]?.FormFields.find(f => f.ComponentName === 'monthlypay')?.ComponentValue;
          // save to contract
          const flowInfosRes = await cloudApiClient.DescribeFlowDetailInfo({
            Agent: agent,
            FlowIds: flowRes.FlowIds || [],
          });

          // logger.info({
          //   action: 'worker/flowInfosRes',
          //   data: { flowInfosRes },
          // });

          // 存储 合同数据
          const saveDatas = (flowInfosRes.FlowInfo || []).map(item => ({
            ...item,
            UserId,
            organizationId: userInfo.organizationId,
            contractStartTime: startDate ? new Date(startDate) : null,
            contractEndTime: endDate ? new Date(endDate) : null,
            monthlyPay: monthlyPay ? Number(monthlyPay) : 0,
            type: 'work-contract',
          }));

          // logger.info({
          //   action: 'worker/saveDatas',
          //   data: { saveDatas },
          // });

          await Promise.all(saveDatas.map(async (item, idx) => {
            const index = params.FlowInfos.findIndex((i) => i.FlowApprovers[1].Mobile === item.FlowApproverInfos[1].Mobile);
            // 存储合同信息
            await contractService.create({ ...item, FlowApproverInfos: JSON.stringify(item.FlowApproverInfos) });
            // 存储员工签署合同记录
            await workerSignRecordService.create({
              id: v4(),
              contractId: item.FlowId,
              workerId: params.FlowInfos[index].FlowApprovers[1].WorkerId,
              status: 'INIT',
              type: 'work-contract',
              startTime: startDate ? new Date(startDate) : null,
              endTime: endDate ? new Date(endDate) : null,
              monthlyPay: monthlyPay ? Number(monthlyPay) : 0,
            });
            // 更新工人签署状态
            await workerService.update(params.FlowInfos[idx].FlowApprovers[1].WorkerId, {
              status: 'INIT',
            });
          }));

          return res.json({ code: 20000, data: saveDatas });
        }
      } catch (error) {
        logger.error({
          action: 'worker/createContracts',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: error.message,
          requestId: error.requestId,
        });
      }
    }
    logger.error({
      action: 'worker/createContracts',
      data: body,
      errMessage: '发起合同失败',
    });
    res.json({
      code: 500,
      message: '发起合同失败',
    });
  });
  // 工人收回派遣
  // sendBack
  app.post(`${process.env.VUE_APP_BASE_API}/worker/sendBack`, async (req, res) => {
    const { userInfo, body } = req;
    const { List } = body;
    if (userInfo) {
      try {
        await Promise.all(List.map(item => sendService.update(item.id, { endTime: new Date(), status: 'FINISH' })));
        await Promise.all(
          List.map(item =>
            sendService.find(item.id).then(record => workerService.update(record.workerId, { status: 'ALL' })),
          ),
        ); // 更新工人状态
        return res.json({
          code: 20000,
          data: { list: body.List },
        });
      } catch (error) {
        logger.error({
          action: 'worker/sendBack',
          data: body,
          errMessage: error,
        });
        return res.json({
          code: 500,
          message: '收回工人派遣失败',
        });
      }
    }
    res.json({
      code: 50204,
      message: '用户登录已过期，请退出重试',
    });
  });
  app.post(`${process.env.VUE_APP_BASE_API}/worker/statics`, async (req, res) => {
    const { userInfo, body } = req;
    const { statusList } = body;
    const result = [];
    if (userInfo) {
      await Promise.all(
        statusList.map(v =>
          workerService
            .filter({
              status: v,
              organizationId: userInfo.organizationId,
            })
            .then(list => {
              result.push(list.length);
            }),
        ),
      );
      return res.json({
        code: 20000,
        data: result,
      });
    }
  });

  app.post(`${process.env.VUE_APP_BASE_API}/worker/cancelFlow`, async (req, res) => {
    const { body, userInfo } = req;
    const { workerId } = body;

    try {
      await workerService.update(workerId, { status: '' }); // 更新工人状态
      const contractList = await workerSignRecordService.search({
        where: {
          workerId,
        },
        limit: 1,
        offset: 0,
      }); // 查找合同记录
      const newest = contractList?.[0];
      await workerSignRecordService.update(newest.id, { status: 'CANCEL' }); // 更新最后一次签署记录
      const params = {
        Agent: mergeAgent({
          ProxyOrganizationOpenId: userInfo.organizationOpenId,
          OpenId: userInfo.openId,
          ProxyAppId: userInfo?.proxyAppId,
        }),
        Version: '2021-05-26',
        FlowId: newest.contractId,
      };
      await cloudApiClient.ChannelCancelFlow(params); // 取消签署流程
      await contractService.update(newest.contractId, { FlowStatus: 'CANCEL' });
      return res.json({
        code: 20000,
      });
    } catch (error) {
      logger.error({
        action: 'worker/cancelFlow',
        data: body,
        errMessage: error,
      });
      return res.json({
        code: 500,
        message: error.message,
        requestId: error.requestId,
      });
    }
  });
  // stopFlow
  app.post(`${process.env.VUE_APP_BASE_API}/worker/stopFlow`, async (req, res) => {
    const { body } = req;
    const { id } = body;

    try {
      await workerService.update(id, { status: '' }); // 更新工人状态
      const contractList = await workerSignRecordService.search({ where:
        {
          workerId: id,
        },
      limit: 1,
      offset: 0,
      }); // 查找合同记录
      const newest = contractList?.[0];
      if (newest) {
        await workerSignRecordService.update(newest.id, { status: 'STOPPED' }); // 更新最后一次签署记录
        await contractService.update(newest.contractId, { FlowStatus: 'STOPPED' });
      }

      return res.json({
        code: 20000,
      });
    } catch (error) {
      logger.error({
        action: 'worker/stopFlow',
        data: body,
        errMessage: error,
      });
      return res.json({
        code: 500,
        message: error.message,
      });
    }
  });
  app.post(`${process.env.VUE_APP_M_BASE_API}/worker/getTenants`, async (req, res) => {
    const { workerId, offset = 0, limit = 10 } = req.body;
    const hash = {};
    const result = [];
    console.log('workerid:', workerId);
    try {
      const sendServiceRecords = await sendService.search({
        where: {
          workerId,
        },
        limit,
        offset,
      });
      await Promise.all(
        sendServiceRecords.map(v =>
          tenantService.find(v.tenantId).then(tenant => {
            if (tenant && !hash[tenant.id]) {
              result.push(tenant);
              hash[tenant.id] = true;
            }
          }),
        ),
      );
      return res.json({
        code: 20000,
        list: result,
      });
    } catch (error) {
      logger.error({
        action: 'worker/getTenants',
        error,
      });
      res.json({
        code: 500,
        message: '获取用工单位失败',
      });
    }
  });
  app.post(`${process.env.VUE_APP_BASE_API}/worker/getProposalContracts`, async (req, res) => {
    const { body } = req;
    const { workerId } = body;
    const workerContractRecords = await workerSignRecordService.search(
      {
        where: {
          workerId,
          type: 'safe-proposal',
        } });
    const safeContracts = [];
    await Promise.all(workerContractRecords.map(record => contractService.find(record.contractId).then(v => {
      if (v.FlowStatus === 'ALL') {
        safeContracts.push(v);
      }
    })));
    if (safeContracts?.length) {
      return res.json({
        code: 20000,
        data: {
          contract: safeContracts[0],
        },
      });
    }
    return res.json({
      code: 20000,
      data: {
        contract: null,
      },
    });
  });

  // 获取安全承诺书签署信息
  app.post(`${process.env.VUE_APP_M_BASE_API}/worker/getProposalContracts`, async (req, res) => {
    const { userInfo } = req;
    const { id } = userInfo;
    const workerContractRecords = await workerSignRecordService.search({
      where: {
        workerId: id,
        type: 'safe-proposal',
      },
    });
    const safeContracts = [];
    await Promise.all(workerContractRecords.map(record => contractService.find(record.contractId).then(v => {
      if (['INIT', 'ALL', 'WILLEXPIRE'].includes(v.FlowStatus)) {
        safeContracts.push(v);
      }
    })));

    if (safeContracts?.length) {
      return res.json({
        code: 20000,
        data: {
          contract: safeContracts[0],
        },
      });
    }
    return res.json({
      code: 20000,
      data: {
        contract: null,
      },
    });
  });
};
